/*      */ package com.zimbra.cs.service.mail;
/*      */ 
/*      */ import com.google.common.base.Objects;
/*      */ import com.zimbra.common.account.Key.AccountBy;
/*      */ import com.zimbra.common.account.Key.DistributionListBy;
/*      */ import com.zimbra.common.calendar.CalendarUtil;
/*      */ import com.zimbra.common.calendar.Geo;
/*      */ import com.zimbra.common.calendar.ICalTimeZone;
/*      */ import com.zimbra.common.calendar.ICalTimeZone.SimpleOnset;
/*      */ import com.zimbra.common.calendar.ParsedDateTime;
/*      */ import com.zimbra.common.calendar.ParsedDuration;
/*      */ import com.zimbra.common.calendar.TZIDMapper;
/*      */ import com.zimbra.common.calendar.TimeZoneMap;
/*      */ import com.zimbra.common.calendar.WellKnownTimeZones;
/*      */ import com.zimbra.common.calendar.ZCalendar.ICalTok;
/*      */ import com.zimbra.common.calendar.ZCalendar.ZCalendarBuilder;
/*      */ import com.zimbra.common.calendar.ZCalendar.ZParameter;
/*      */ import com.zimbra.common.calendar.ZCalendar.ZProperty;
/*      */ import com.zimbra.common.calendar.ZCalendar.ZVCalendar;
/*      */ import com.zimbra.common.localconfig.DebugConfig;
/*      */ import com.zimbra.common.localconfig.KnownKey;
/*      */ import com.zimbra.common.localconfig.LC;
/*      */ import com.zimbra.common.service.ServiceException;
/*      */ import com.zimbra.common.soap.Element;
/*      */ import com.zimbra.common.util.L10nUtil;
/*      */ import com.zimbra.common.util.L10nUtil.MsgKey;
/*      */ import com.zimbra.common.util.Log;
/*      */ import com.zimbra.common.util.ZimbraLog;
/*      */ import com.zimbra.cs.account.Account;
/*      */ import com.zimbra.cs.account.DistributionList;
/*      */ import com.zimbra.cs.account.Provisioning;
/*      */ import com.zimbra.cs.gal.GalGroup;
/*      */ import com.zimbra.cs.gal.GalGroupMembers;
/*      */ import com.zimbra.cs.index.SortBy;
/*      */ import com.zimbra.cs.ldap.LdapUtil;
/*      */ import com.zimbra.cs.mailbox.CalendarItem;
/*      */ import com.zimbra.cs.mailbox.CalendarItem.ReplyInfo;
/*      */ import com.zimbra.cs.mailbox.Folder;
/*      */ import com.zimbra.cs.mailbox.MailItem.Type;
/*      */ import com.zimbra.cs.mailbox.Mailbox;
/*      */ import com.zimbra.cs.mailbox.MailboxManager;
/*      */ import com.zimbra.cs.mailbox.calendar.Alarm;
/*      */ import com.zimbra.cs.mailbox.calendar.CalendarMailSender;
/*      */ import com.zimbra.cs.mailbox.calendar.IcalXmlStrMap;
/*      */ import com.zimbra.cs.mailbox.calendar.Invite;
/*      */ import com.zimbra.cs.mailbox.calendar.Period;
/*      */ import com.zimbra.cs.mailbox.calendar.RdateExdate;
/*      */ import com.zimbra.cs.mailbox.calendar.RecurId;
/*      */ import com.zimbra.cs.mailbox.calendar.Recurrence.ExceptionRule;
/*      */ import com.zimbra.cs.mailbox.calendar.Recurrence.IRecurrence;
/*      */ import com.zimbra.cs.mailbox.calendar.Recurrence.RecurrenceRule;
/*      */ import com.zimbra.cs.mailbox.calendar.Recurrence.SimpleRepeatingRule;
/*      */ import com.zimbra.cs.mailbox.calendar.Recurrence.SingleDates;
/*      */ import com.zimbra.cs.mailbox.calendar.Util;
/*      */ import com.zimbra.cs.mailbox.calendar.ZAttendee;
/*      */ import com.zimbra.cs.mailbox.calendar.ZOrganizer;
/*      */ import com.zimbra.cs.mailbox.calendar.ZRecur;
/*      */ import com.zimbra.cs.mailbox.util.TypedIdList;
/*      */ import com.zimbra.cs.util.AccountUtil.AccountAddressMatcher;
/*      */ import com.zimbra.soap.base.CalTZInfoInterface;
/*      */ import com.zimbra.soap.type.TzOnsetInfo;
/*      */ import java.text.ParseException;
/*      */ import java.util.ArrayList;
/*      */ import java.util.Date;
/*      */ import java.util.HashSet;
/*      */ import java.util.Iterator;
/*      */ import java.util.List;
/*      */ import java.util.Locale;
/*      */ import java.util.Set;
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ public class CalendarUtils
/*      */ {
/*      */   public static final long MICROSOFT_EPOC_START_MS_SINCE_EPOC = -11644473600000L;
/*      */   public static final boolean RECUR_NOT_ALLOWED = false;
/*      */   public static final boolean RECUR_ALLOWED = true;
/*      */   
/*      */   static ParseMimeMessage.InviteParserResult parseInviteRaw(Account account, Element inviteElem)
/*      */     throws ServiceException
/*      */   {
/*  105 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*      */     
/*  107 */     Element content = inviteElem.getElement("content");
/*  108 */     toRet.mUid = content.getAttribute("uid");
/*  109 */     toRet.mSummary = content.getAttribute("summary");
/*  110 */     toRet.mCal = ZCalendar.ZCalendarBuilder.build(content.getText());
/*      */     
/*  112 */     List<Invite> invs = Invite.createFromCalendar(account, toRet.mSummary, toRet.mCal, false);
/*      */     
/*      */ 
/*  115 */     toRet.mInvite = ((Invite)invs.get(0));
/*      */     
/*  117 */     return toRet;
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   static ParseMimeMessage.InviteParserResult parseInviteForCreate(Account account, MailItem.Type type, Element inviteElem, TimeZoneMap tzMap, String uid, boolean recurrenceIdAllowed, boolean recurAllowed)
/*      */     throws ServiceException
/*      */   {
/*  141 */     if (tzMap == null) {
/*  142 */       tzMap = new TimeZoneMap(Util.getAccountTimeZone(account));
/*      */     }
/*  144 */     Invite create = new Invite(ZCalendar.ICalTok.PUBLISH.toString(), tzMap, false);
/*  145 */     create.setSentByMe(true);
/*      */     
/*  147 */     parseInviteElementCommon(account, type, inviteElem, create, recurrenceIdAllowed, recurAllowed);
/*      */     
/*      */ 
/*  150 */     if (create.getDTStamp() == 0L) {
/*  151 */       create.setDtStamp(new Date().getTime());
/*      */     }
/*      */     
/*      */ 
/*  155 */     if ((uid != null) && (uid.length() > 0)) {
/*  156 */       create.setUid(uid);
/*      */     } else {
/*  158 */       String uidParsed = create.getUid();
/*  159 */       if ((uidParsed == null) || (uidParsed.length() == 0)) {
/*  160 */         create.setUid(LdapUtil.generateUUID());
/*      */       }
/*      */     }
/*  163 */     ZCalendar.ZVCalendar iCal = create.newToICalendar(true);
/*      */     
/*  165 */     String summaryStr = create.getName() != null ? create.getName() : "";
/*      */     
/*  167 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*  168 */     toRet.mCal = iCal;
/*  169 */     toRet.mUid = create.getUid();
/*  170 */     toRet.mSummary = summaryStr;
/*  171 */     toRet.mInvite = create;
/*      */     
/*  173 */     return toRet;
/*      */   }
/*      */   
/*      */   private static String parseInviteChanges(Element inviteElem) {
/*  177 */     Element compElem = inviteElem.getOptionalElement("comp");
/*  178 */     if (compElem == null)
/*  179 */       compElem = inviteElem;
/*  180 */     String changes = compElem.getAttribute("changes", null);
/*  181 */     if ((changes != null) && (changes.length() > 0)) {
/*  182 */       return changes;
/*      */     }
/*  184 */     return null;
/*      */   }
/*      */   
/*      */   static ParseMimeMessage.InviteParserResult parseInviteForCreateException(Account account, MailItem.Type type, Element inviteElem, TimeZoneMap tzMap, String uid, Invite defaultInv) throws ServiceException
/*      */   {
/*  189 */     if (tzMap == null) {
/*  190 */       tzMap = new TimeZoneMap(Util.getAccountTimeZone(account));
/*      */     }
/*  192 */     Invite create = new Invite(ZCalendar.ICalTok.PUBLISH.toString(), tzMap, false);
/*  193 */     create.setSentByMe(true);
/*      */     
/*  195 */     parseInviteElementCommon(account, type, inviteElem, create, true, false);
/*      */     
/*      */ 
/*  198 */     if (create.getDTStamp() == 0L) {
/*  199 */       create.setDtStamp(new Date().getTime());
/*      */     }
/*      */     
/*      */ 
/*  203 */     if ((uid != null) && (uid.length() > 0)) {
/*  204 */       create.setUid(uid);
/*      */     }
/*      */     
/*  207 */     create.setSeqNo(Math.max(create.getSeqNo(), defaultInv.getSeqNo() + 1));
/*      */     
/*      */ 
/*  210 */     create.setOrganizer(defaultInv.hasOrganizer() ? new ZOrganizer(defaultInv.getOrganizer()) : null);
/*      */     
/*  212 */     create.setIsOrganizer(account);
/*      */     
/*      */ 
/*  215 */     String changes = parseInviteChanges(inviteElem);
/*  216 */     if (changes != null)
/*      */     {
/*  218 */       create.addXProp(new ZCalendar.ZProperty(ZCalendar.ICalTok.X_ZIMBRA_CHANGES, changes));
/*      */     }
/*  220 */     ZCalendar.ZVCalendar iCal = create.newToICalendar(true);
/*  221 */     create.removeXProp(ZCalendar.ICalTok.X_ZIMBRA_CHANGES.toString());
/*      */     
/*  223 */     String summaryStr = create.getName() != null ? create.getName() : "";
/*      */     
/*  225 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*  226 */     toRet.mCal = iCal;
/*  227 */     toRet.mUid = create.getUid();
/*  228 */     toRet.mSummary = summaryStr;
/*  229 */     toRet.mInvite = create;
/*      */     
/*  231 */     return toRet;
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   static ParseMimeMessage.InviteParserResult parseInviteForModify(Account account, MailItem.Type type, Element inviteElem, Invite oldInv, Invite seriesInv, List<ZAttendee> attendeesAdded, List<ZAttendee> attendeesToCancel, boolean recurAllowed)
/*      */     throws ServiceException
/*      */   {
/*  246 */     Invite mod = new Invite(ZCalendar.ICalTok.PUBLISH.toString(), oldInv.getTimeZoneMap(), false);
/*  247 */     mod.setSentByMe(true);
/*      */     
/*  249 */     parseInviteElementCommon(account, type, inviteElem, mod, oldInv.hasRecurId(), recurAllowed);
/*      */     
/*      */ 
/*  252 */     mod.setUid(oldInv.getUid());
/*      */     
/*  254 */     attendeesToCancel.addAll(getRemovedAttendees(oldInv.getAttendees(), mod.getAttendees(), true, account));
/*  255 */     attendeesAdded.addAll(getRemovedAttendees(mod.getAttendees(), oldInv.getAttendees(), false, account));
/*      */     
/*      */ 
/*  258 */     if (mod.isOrganizer())
/*      */     {
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*  264 */       int seriesSeq = seriesInv != null ? seriesInv.getSeqNo() : 0;
/*  265 */       int newSeq = Math.max(Math.max(mod.getSeqNo(), oldInv.getSeqNo() + 1), seriesSeq);
/*      */       
/*      */ 
/*      */ 
/*  269 */       if (!attendeesToCancel.isEmpty())
/*  270 */         newSeq++;
/*  271 */       mod.setSeqNo(newSeq);
/*  272 */       mod.setDtStamp(new Date().getTime());
/*      */ 
/*      */     }
/*      */     else
/*      */     {
/*  277 */       mod.setSeqNo(oldInv.getSeqNo());
/*  278 */       mod.setDtStamp(oldInv.getDTStamp());
/*      */     }
/*      */     
/*  281 */     if (oldInv.hasRecurId()) {
/*  282 */       mod.setRecurId(oldInv.getRecurId());
/*      */     }
/*      */     
/*      */ 
/*  286 */     String changes = parseInviteChanges(inviteElem);
/*  287 */     if (changes != null)
/*      */     {
/*  289 */       mod.addXProp(new ZCalendar.ZProperty(ZCalendar.ICalTok.X_ZIMBRA_CHANGES, changes));
/*      */     }
/*  291 */     ZCalendar.ZVCalendar iCal = mod.newToICalendar(true);
/*  292 */     mod.removeXProp(ZCalendar.ICalTok.X_ZIMBRA_CHANGES.toString());
/*      */     
/*  294 */     String summaryStr = "";
/*  295 */     if (mod.getName() != null) {
/*  296 */       summaryStr = mod.getName();
/*      */     }
/*      */     
/*  299 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*  300 */     toRet.mCal = iCal;
/*  301 */     toRet.mUid = mod.getUid();
/*  302 */     toRet.mSummary = summaryStr;
/*  303 */     toRet.mInvite = mod;
/*      */     
/*  305 */     return toRet;
/*      */   }
/*      */   
/*      */   static ParseMimeMessage.InviteParserResult parseInviteForCancel(Account account, Folder folder, MailItem.Type type, Element inviteElem, TimeZoneMap tzMap, boolean recurrenceIdAllowed, boolean recurAllowed)
/*      */     throws ServiceException
/*      */   {
/*  311 */     if (tzMap == null) {
/*  312 */       tzMap = new TimeZoneMap(Util.getAccountTimeZone(account));
/*      */     }
/*  314 */     Invite cancel = new Invite(ZCalendar.ICalTok.CANCEL.toString(), tzMap, false);
/*  315 */     cancel.setSentByMe(true);
/*      */     
/*  317 */     parseInviteElementCommon(account, type, inviteElem, cancel, recurrenceIdAllowed, recurAllowed);
/*      */     
/*      */ 
/*  320 */     String uid = cancel.getUid();
/*  321 */     if ((uid == null) || (uid.length() == 0)) {
/*  322 */       throw ServiceException.INVALID_REQUEST("Missing uid in a cancel invite", null);
/*      */     }
/*  324 */     Invite sanitized = cancelInvite(account, null, false, false, folder, cancel, null, cancel.getAttendees(), cancel.getRecurId(), false);
/*      */     
/*      */ 
/*      */ 
/*      */ 
/*  329 */     sanitized.setInviteId(cancel.getMailItemId());
/*  330 */     sanitized.setDtStamp(cancel.getDTStamp());
/*      */     
/*  332 */     ZCalendar.ZVCalendar iCal = sanitized.newToICalendar(true);
/*      */     
/*  334 */     String summaryStr = sanitized.getName() != null ? sanitized.getName() : "";
/*      */     
/*  336 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*  337 */     toRet.mCal = iCal;
/*  338 */     toRet.mUid = sanitized.getUid();
/*  339 */     toRet.mSummary = summaryStr;
/*  340 */     toRet.mInvite = sanitized;
/*      */     
/*  342 */     return toRet;
/*      */   }
/*      */   
/*      */   static ParseMimeMessage.InviteParserResult parseInviteForAddInvite(Account account, MailItem.Type type, Element inviteElem, TimeZoneMap tzMap) throws ServiceException
/*      */   {
/*  347 */     if (tzMap == null)
/*  348 */       tzMap = new TimeZoneMap(Util.getAccountTimeZone(account));
/*  349 */     Invite inv = new Invite(ZCalendar.ICalTok.PUBLISH.toString(), tzMap, false);
/*      */     
/*  351 */     parseInviteElementCommon(account, type, inviteElem, inv, true, true);
/*      */     
/*  353 */     String uid = inv.getUid();
/*  354 */     if ((uid == null) || (uid.length() == 0)) {
/*  355 */       throw ServiceException.INVALID_REQUEST("Missing uid in an add invite", null);
/*      */     }
/*      */     
/*  358 */     if (inv.getDTStamp() == 0L) {
/*  359 */       inv.setDtStamp(new Date().getTime());
/*      */     }
/*      */     
/*  362 */     ZCalendar.ZVCalendar iCal = inv.newToICalendar(true);
/*      */     
/*  364 */     String summaryStr = inv.getName() != null ? inv.getName() : "";
/*      */     
/*  366 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*  367 */     toRet.mCal = iCal;
/*  368 */     toRet.mUid = inv.getUid();
/*  369 */     toRet.mSummary = summaryStr;
/*  370 */     toRet.mInvite = inv;
/*      */     
/*  372 */     return toRet;
/*      */   }
/*      */   
/*      */   static ParseMimeMessage.InviteParserResult parseInviteForCounter(Account account, Invite oldInvite, MailItem.Type type, Element inviteElem) throws ServiceException
/*      */   {
/*  377 */     TimeZoneMap tzMap = new TimeZoneMap(Util.getAccountTimeZone(account));
/*  378 */     Invite inv = new Invite(ZCalendar.ICalTok.COUNTER.toString(), tzMap, false);
/*      */     
/*  380 */     parseInviteElementCommon(account, type, inviteElem, inv, true, true);
/*      */     
/*      */ 
/*  383 */     if (oldInvite == null) {
/*  384 */       Mailbox mbox = MailboxManager.getInstance().getMailboxByAccount(account);
/*  385 */       CalendarItem calItem = mbox.getCalendarItemByUid(null, inv.getUid());
/*  386 */       if (calItem != null) {
/*  387 */         oldInvite = calItem.getInvite(inv.getRecurId());
/*      */       }
/*      */     }
/*  390 */     if (oldInvite != null)
/*      */     {
/*  392 */       inv.getTimeZoneMap().add(oldInvite.getTimeZoneMap());
/*      */       
/*  394 */       ParsedDateTime dt = oldInvite.getStartTime();
/*  395 */       if (dt != null) {
/*  396 */         ZCalendar.ZProperty prop = new ZCalendar.ZProperty("X-MS-OLK-ORIGINALSTART");
/*  397 */         prop.setValue(dt.getDateTimePartString());
/*  398 */         if (dt.getTZName() != null)
/*  399 */           prop.addParameter(new ZCalendar.ZParameter(ZCalendar.ICalTok.TZID, dt.getTZName()));
/*  400 */         inv.addXProp(prop);
/*      */       }
/*      */       
/*  403 */       dt = oldInvite.getEffectiveEndTime();
/*  404 */       if (dt != null) {
/*  405 */         ZCalendar.ZProperty prop = new ZCalendar.ZProperty("X-MS-OLK-ORIGINALEND");
/*  406 */         prop.setValue(dt.getDateTimePartString());
/*  407 */         if (dt.getTZName() != null)
/*  408 */           prop.addParameter(new ZCalendar.ZParameter(ZCalendar.ICalTok.TZID, dt.getTZName()));
/*  409 */         inv.addXProp(prop);
/*      */       }
/*      */       
/*  412 */       if ((inv.getLocation() == null) || (inv.getLocation().isEmpty())) {
/*  413 */         inv.setLocation(oldInvite.getLocation());
/*      */       }
/*      */     }
/*      */     
/*  417 */     String uid = inv.getUid();
/*  418 */     if ((uid == null) || (uid.length() == 0)) {
/*  419 */       throw ServiceException.INVALID_REQUEST("Missing uid in a counter invite", null);
/*      */     }
/*      */     
/*  422 */     if (!inv.hasOrganizer()) {
/*  423 */       throw ServiceException.INVALID_REQUEST("Missing organizer in a counter invite", null);
/*      */     }
/*      */     
/*  426 */     if (inv.getDTStamp() == 0L) {
/*  427 */       inv.setDtStamp(new Date().getTime());
/*      */     }
/*      */     
/*      */ 
/*  431 */     if (inv.getStartTime() == null) {
/*  432 */       throw ServiceException.INVALID_REQUEST("Missing dtstart in a counter invite", null);
/*      */     }
/*      */     
/*      */ 
/*  436 */     if (!inv.hasOtherAttendees()) {
/*  437 */       ZAttendee at = new ZAttendee(account.getMail());
/*  438 */       at.setPartStat("TE");
/*  439 */       inv.addAttendee(at);
/*      */     }
/*      */     
/*  442 */     inv.setLocalOnly(false);
/*  443 */     ZCalendar.ZVCalendar iCal = inv.newToICalendar(true);
/*      */     
/*  445 */     String summaryStr = inv.getName() != null ? inv.getName() : "";
/*      */     
/*  447 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*  448 */     toRet.mCal = iCal;
/*  449 */     toRet.mUid = inv.getUid();
/*  450 */     toRet.mSummary = summaryStr;
/*  451 */     toRet.mInvite = inv;
/*      */     
/*  453 */     return toRet;
/*      */   }
/*      */   
/*      */   static ParseMimeMessage.InviteParserResult parseInviteForDeclineCounter(Account account, MailItem.Type type, Element inviteElem) throws ServiceException
/*      */   {
/*  458 */     TimeZoneMap tzMap = new TimeZoneMap(Util.getAccountTimeZone(account));
/*  459 */     Invite inv = new Invite(ZCalendar.ICalTok.DECLINECOUNTER.toString(), tzMap, false);
/*      */     
/*  461 */     parseInviteElementCommon(account, type, inviteElem, inv, true, true);
/*      */     
/*      */ 
/*  464 */     String uid = inv.getUid();
/*  465 */     if ((uid == null) || (uid.length() == 0)) {
/*  466 */       throw ServiceException.INVALID_REQUEST("Missing uid in a decline counter invite", null);
/*      */     }
/*      */     
/*  469 */     if (!inv.hasOrganizer()) {
/*  470 */       throw ServiceException.INVALID_REQUEST("Missing organizer in a decline counter invite", null);
/*      */     }
/*      */     
/*  473 */     if (inv.getDTStamp() == 0L) {
/*  474 */       inv.setDtStamp(new Date().getTime());
/*      */     }
/*      */     
/*  477 */     inv.setLocalOnly(false);
/*  478 */     ZCalendar.ZVCalendar iCal = inv.newToICalendar(true);
/*      */     
/*  480 */     String summaryStr = inv.getName() != null ? inv.getName() : "";
/*      */     
/*  482 */     ParseMimeMessage.InviteParserResult toRet = new ParseMimeMessage.InviteParserResult();
/*  483 */     toRet.mCal = iCal;
/*  484 */     toRet.mUid = inv.getUid();
/*  485 */     toRet.mSummary = summaryStr;
/*  486 */     toRet.mInvite = inv;
/*      */     
/*  488 */     return toRet;
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */   public static List<ZAttendee> getRemovedAttendees(List<ZAttendee> oldAttendees, List<ZAttendee> newAttendees, boolean checkListMembership, Account account)
/*      */     throws ServiceException
/*      */   {
/*  496 */     List<ZAttendee> list = new ArrayList();
/*  497 */     Provisioning prov = Provisioning.getInstance();
/*      */     
/*      */ 
/*  500 */     for (ZAttendee old : oldAttendees) {
/*  501 */       boolean matches = false;
/*  502 */       String oldAddr = old.getAddress();
/*  503 */       if (oldAddr != null) {
/*  504 */         Account oldAcct = prov.get(Key.AccountBy.name, oldAddr);
/*  505 */         AccountUtil.AccountAddressMatcher acctMatcher; if (oldAcct != null)
/*      */         {
/*  507 */           acctMatcher = new AccountUtil.AccountAddressMatcher(oldAcct);
/*  508 */           for (ZAttendee newAt : newAttendees) {
/*  509 */             if (acctMatcher.matches(newAt.getAddress())) {
/*  510 */               matches = true;
/*  511 */               break;
/*      */             }
/*      */           }
/*      */         }
/*      */         else {
/*  516 */           for (ZAttendee newAt : newAttendees) {
/*  517 */             if (oldAddr.equalsIgnoreCase(newAt.getAddress())) {
/*  518 */               matches = true;
/*  519 */               break;
/*      */             }
/*      */           }
/*      */         }
/*      */       }
/*  524 */       if (!matches)
/*  525 */         list.add(old);
/*      */     }
/*  527 */     if (list.isEmpty()) {
/*  528 */       return list;
/*      */     }
/*      */     
/*  531 */     checkListMembership = (checkListMembership) && (LC.check_dl_membership_enabled.booleanValue());
/*      */     Set<String> remoteAddrs;
/*  533 */     if (checkListMembership) {
/*  534 */       List<DistributionList> newAtsDL = new ArrayList();
/*  535 */       List<String> newAtsGALGroup = new ArrayList();
/*  536 */       for (ZAttendee at : newAttendees) {
/*  537 */         String addr = at.getAddress();
/*  538 */         if (addr != null) {
/*  539 */           DistributionList dl = prov.get(Key.DistributionListBy.name, addr);
/*  540 */           if (dl != null) {
/*  541 */             newAtsDL.add(dl);
/*  542 */           } else if (GalGroup.isGroup(addr, account)) {
/*  543 */             newAtsGALGroup.add(addr);
/*      */           }
/*      */         }
/*      */       }
/*      */       
/*      */ 
/*      */ 
/*      */ 
/*  551 */       for (String galAddr : newAtsGALGroup) {
/*  552 */         if (list.isEmpty())
/*      */           break;
/*  554 */         galMembers = GalGroupMembers.getGroupMembers(galAddr, account);
/*  555 */         for (removedIter = list.iterator(); removedIter.hasNext();) {
/*  556 */           ZAttendee removedAt = (ZAttendee)removedIter.next();
/*  557 */           String addr = removedAt.getAddress();
/*  558 */           if ((addr != null) && (galMembers.contains(addr)))
/*  559 */             removedIter.remove();
/*      */         } }
/*      */       Set<String> galMembers;
/*      */       Iterator<ZAttendee> removedIter;
/*  563 */       remoteAddrs = new HashSet();
/*      */       
/*      */ 
/*      */ 
/*      */ 
/*  568 */       for (Iterator<ZAttendee> removedIter = list.iterator(); removedIter.hasNext();) {
/*  569 */         ZAttendee removedAt = (ZAttendee)removedIter.next();
/*  570 */         String addr = removedAt.getAddress();
/*  571 */         if (addr != null) {
/*  572 */           Account removedAcct = prov.get(Key.AccountBy.name, addr);
/*  573 */           Set<String> acctDLs; if (removedAcct != null) {
/*  574 */             acctDLs = prov.getDistributionLists(removedAcct);
/*  575 */             for (DistributionList dl : newAtsDL) {
/*  576 */               if (acctDLs.contains(dl.getId())) {
/*  577 */                 removedIter.remove();
/*  578 */                 break;
/*      */               }
/*      */             }
/*      */           }
/*      */           else {
/*  583 */             remoteAddrs.add(addr);
/*      */           }
/*      */         }
/*      */       }
/*      */       
/*      */ 
/*  589 */       if (!remoteAddrs.isEmpty())
/*  590 */         for (DistributionList dl : newAtsDL)
/*      */         {
/*  592 */           String[] members = dl.getAllMembers();
/*  593 */           if ((members != null) && (members.length > 0)) {
/*  594 */             membersLower = new HashSet();
/*  595 */             for (String member : members) {
/*  596 */               membersLower.add(member.toLowerCase());
/*      */             }
/*  598 */             for (removedIter = list.iterator(); removedIter.hasNext();) {
/*  599 */               ZAttendee removedAt = (ZAttendee)removedIter.next();
/*  600 */               String addr = removedAt.getAddress();
/*  601 */               if ((addr != null) && (remoteAddrs.contains(addr)) && (membersLower.contains(addr.toLowerCase())))
/*  602 */                 removedIter.remove();
/*      */             }
/*      */           }
/*      */         }
/*      */     }
/*      */     Set<String> membersLower;
/*      */     Iterator<ZAttendee> removedIter;
/*  609 */     return list;
/*      */   }
/*      */   
/*      */   static RecurId parseRecurId(Element e, TimeZoneMap tzmap) throws ServiceException {
/*  613 */     String range = e.getAttribute("range", null);
/*      */     
/*  615 */     ParsedDateTime dt = parseDateTime(e, tzmap);
/*  616 */     return new RecurId(dt, range);
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   static ParsedDateTime parseDateTime(Element e, TimeZoneMap invTzMap)
/*      */     throws ServiceException
/*      */   {
/*  629 */     String d = e.getAttribute("d", null);
/*  630 */     String tz = e.getAttribute("tz", null);
/*  631 */     return parseDateTime(e.getName(), d, tz, invTzMap);
/*      */   }
/*      */   
/*      */   private static ParsedDateTime parseDateTime(String eltName, String d, String tzName, TimeZoneMap invTzMap) throws ServiceException
/*      */   {
/*      */     try
/*      */     {
/*  638 */       ICalTimeZone zone = null;
/*  639 */       if (tzName != null) {
/*  640 */         zone = lookupAndAddToTzList(tzName, invTzMap, null);
/*      */       }
/*  642 */       ICalTimeZone localTz = invTzMap != null ? invTzMap.getLocalTimeZone() : null;
/*  643 */       return ParsedDateTime.parse(d, invTzMap, zone, localTz);
/*      */     } catch (ParseException ex) {
/*  645 */       throw ServiceException.INVALID_REQUEST("could not parse time " + d + " in element " + eltName, ex);
/*      */     }
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */   private static ICalTimeZone lookupAndAddToTzList(String tzId, TimeZoneMap invTzMap, Invite inv)
/*      */     throws ServiceException
/*      */   {
/*  654 */     int len = tzId.length();
/*  655 */     if ((len >= 2) && (tzId.charAt(0) == '"') && (tzId.charAt(len - 1) == '"')) {
/*  656 */       tzId = tzId.substring(1, len - 1);
/*      */     }
/*      */     
/*  659 */     ICalTimeZone zone = null;
/*      */     
/*  661 */     if (tzId.equals("")) {
/*  662 */       return null;
/*      */     }
/*      */     
/*  665 */     if (!DebugConfig.disableCalendarTZMatchByID) {
/*  666 */       tzId = TZIDMapper.canonicalize(tzId);
/*      */     }
/*  668 */     zone = WellKnownTimeZones.getTimeZoneById(tzId);
/*      */     
/*  670 */     if (zone == null)
/*      */     {
/*      */ 
/*  673 */       if (invTzMap != null) {
/*  674 */         zone = invTzMap.getTimeZone(tzId);
/*      */       }
/*      */       
/*  677 */       if (zone == null) {
/*  678 */         throw ServiceException.INVALID_REQUEST("invalid time zone \"" + tzId + "\"", null);
/*      */       }
/*      */     }
/*  681 */     if ((inv != null) && (!inv.getTimeZoneMap().contains(zone)))
/*  682 */       inv.getTimeZoneMap().add(zone);
/*  683 */     return zone;
/*      */   }
/*      */   
/*      */ 
/*      */   static Recurrence.IRecurrence parseRecur(Element recurElt, TimeZoneMap invTzMap, ParsedDateTime dtStart, ParsedDateTime dtEnd, ParsedDuration dur, RecurId recurId)
/*      */     throws ServiceException
/*      */   {
/*  690 */     if ((dur == null) && (dtStart != null) && (dtEnd != null)) {
/*  691 */       dur = dtEnd.difference(dtStart);
/*      */     }
/*  693 */     ArrayList<Recurrence.IRecurrence> addRules = new ArrayList();
/*  694 */     ArrayList<Recurrence.IRecurrence> subRules = new ArrayList();
/*      */     
/*  696 */     for (Iterator iter = recurElt.elementIterator(); iter.hasNext();) {
/*  697 */       e = (Element)iter.next();
/*      */       
/*  699 */       exclude = false;
/*      */       
/*  701 */       if (e.getName().equals("exclude")) {
/*  702 */         exclude = true;
/*      */       } else {
/*  704 */         if (!e.getName().equals("add")) {
/*      */           continue;
/*      */         }
/*      */       }
/*      */       
/*  709 */       for (intIter = e.elementIterator(); intIter.hasNext();)
/*      */       {
/*  711 */         Element intElt = (Element)intIter.next();
/*      */         
/*  713 */         if (intElt.getName().equals("dates"))
/*      */         {
/*  715 */           String tzid = intElt.getAttribute("tz", null);
/*  716 */           ICalTimeZone tz = tzid != null ? invTzMap.lookupAndAdd(tzid) : null;
/*  717 */           RdateExdate rexdate = new RdateExdate(exclude ? ZCalendar.ICalTok.EXDATE : ZCalendar.ICalTok.RDATE, tz);
/*      */           
/*  719 */           ZCalendar.ICalTok valueType = null;
/*  720 */           Iterator<Element> dtvalIter = intElt.elementIterator("dtval");
/*  721 */           while (dtvalIter.hasNext()) {
/*  722 */             ZCalendar.ICalTok dtvalValueType = null;
/*  723 */             Element dtvalElem = (Element)dtvalIter.next();
/*  724 */             Element dtvalStartElem = dtvalElem.getElement("s");
/*  725 */             String dtvalStartDateStr = dtvalStartElem.getAttribute("d");
/*  726 */             ParsedDateTime dtvalStart = parseDateTime(dtvalElem.getName(), dtvalStartDateStr, tzid, invTzMap);
/*      */             
/*      */ 
/*  729 */             Element dtvalEndElem = dtvalElem.getOptionalElement("e");
/*  730 */             Element dtvalDurElem = dtvalElem.getOptionalElement("dur");
/*  731 */             if ((dtvalEndElem == null) && (dtvalDurElem == null)) {
/*  732 */               if (dtvalStart.hasTime()) {
/*  733 */                 dtvalValueType = ZCalendar.ICalTok.DATE_TIME;
/*      */               } else
/*  735 */                 dtvalValueType = ZCalendar.ICalTok.DATE;
/*  736 */               rexdate.addValue(dtvalStart);
/*      */             } else {
/*  738 */               dtvalValueType = ZCalendar.ICalTok.PERIOD;
/*  739 */               if (dtvalEndElem != null) {
/*  740 */                 String dtvalEndDateStr = dtvalEndElem.getAttribute("d");
/*  741 */                 ParsedDateTime dtvalEnd = parseDateTime(dtvalElem.getName(), dtvalEndDateStr, tzid, invTzMap);
/*      */                 
/*  743 */                 Period p = new Period(dtvalStart, dtvalEnd);
/*  744 */                 rexdate.addValue(p);
/*      */               } else {
/*  746 */                 ParsedDuration d = ParsedDuration.parse(dtvalDurElem);
/*  747 */                 Period p = new Period(dtvalStart, d);
/*  748 */                 rexdate.addValue(p);
/*      */               }
/*      */             }
/*      */             
/*  752 */             if (valueType == null) {
/*  753 */               valueType = dtvalValueType;
/*  754 */               rexdate.setValueType(valueType);
/*  755 */             } else if (valueType != dtvalValueType) {
/*  756 */               throw ServiceException.INVALID_REQUEST("Cannot mix different value types in a single <" + intElt.getName() + "> element", null);
/*      */             }
/*      */           }
/*      */           
/*      */ 
/*  761 */           Recurrence.SingleDates sd = new Recurrence.SingleDates(rexdate, dur);
/*  762 */           if (exclude) {
/*  763 */             subRules.add(sd);
/*      */           } else {
/*  765 */             addRules.add(sd);
/*      */           }
/*  767 */         } else if (intElt.getName().equals("rule"))
/*      */         {
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*  773 */           StringBuilder recurBuf = new StringBuilder(100);
/*      */           
/*  775 */           String freq = IcalXmlStrMap.sFreqMap.toIcal(intElt.getAttribute("freq"));
/*      */           
/*  777 */           recurBuf.append("FREQ=").append(freq);
/*      */           
/*  779 */           for (Iterator ruleIter = intElt.elementIterator(); ruleIter.hasNext();) {
/*  780 */             Element ruleElt = (Element)ruleIter.next();
/*  781 */             String ruleEltName = ruleElt.getName();
/*  782 */             if (ruleEltName.equals("until")) {
/*  783 */               recurBuf.append(";UNTIL=");
/*  784 */               String d = ruleElt.getAttribute("d");
/*  785 */               recurBuf.append(d);
/*      */               
/*      */ 
/*      */ 
/*      */ 
/*  790 */               if ((d.indexOf("T") >= 0) && 
/*  791 */                 (d.indexOf("Z") < 0)) {
/*  792 */                 recurBuf.append('Z');
/*      */               }
/*      */             }
/*  795 */             else if (ruleEltName.equals("count")) {
/*  796 */               int num = (int)ruleElt.getAttributeLong("num", -1L);
/*  797 */               if (num > 0) {
/*  798 */                 recurBuf.append(";COUNT=").append(num);
/*      */               } else {
/*  800 */                 throw ServiceException.INVALID_REQUEST("Expected positive num attribute in <recur> <rule> <count>", null);
/*      */               }
/*      */             }
/*  803 */             else if (ruleEltName.equals("interval")) {
/*  804 */               String ival = ruleElt.getAttribute("ival");
/*  805 */               recurBuf.append(";INTERVAL=").append(ival);
/*  806 */             } else if (ruleEltName.equals("bysecond")) {
/*  807 */               String list = ruleElt.getAttribute("seclist");
/*  808 */               recurBuf.append(";BYSECOND=").append(list);
/*  809 */             } else if (ruleEltName.equals("byminute")) {
/*  810 */               String list = ruleElt.getAttribute("minlist");
/*  811 */               recurBuf.append(";BYMINUTE=").append(list);
/*  812 */             } else if (ruleEltName.equals("byhour")) {
/*  813 */               String list = ruleElt.getAttribute("hrlist");
/*  814 */               recurBuf.append(";BYHOUR=").append(list);
/*  815 */             } else if (ruleEltName.equals("byday")) {
/*  816 */               recurBuf.append(";BYDAY=");
/*  817 */               int pos = 0;
/*  818 */               Iterator bydayIter = ruleElt.elementIterator("wkday");
/*  819 */               for (; bydayIter.hasNext(); 
/*  820 */                   pos++) {
/*  821 */                 Element wkdayElt = (Element)bydayIter.next();
/*  822 */                 if (pos > 0)
/*  823 */                   recurBuf.append(",");
/*  824 */                 String ordwk = wkdayElt.getAttribute("ordwk", null);
/*  825 */                 if (ordwk != null)
/*  826 */                   recurBuf.append(ordwk);
/*  827 */                 String day = wkdayElt.getAttribute("day");
/*  828 */                 if ((day == null) || (day.length() == 0)) {
/*  829 */                   throw ServiceException.INVALID_REQUEST("Missing day in <" + ruleEltName + ">", null);
/*      */                 }
/*      */                 
/*      */ 
/*  833 */                 recurBuf.append(day);
/*      */               }
/*  835 */             } else if (ruleEltName.equals("bymonthday")) {
/*  836 */               String list = ruleElt.getAttribute("modaylist");
/*  837 */               recurBuf.append(";BYMONTHDAY=").append(list);
/*  838 */             } else if (ruleEltName.equals("byyearday")) {
/*  839 */               String list = ruleElt.getAttribute("yrdaylist");
/*  840 */               recurBuf.append(";BYYEARDAY=").append(list);
/*  841 */             } else if (ruleEltName.equals("byweekno")) {
/*  842 */               String list = ruleElt.getAttribute("wklist");
/*  843 */               recurBuf.append(";BYWEEKNO=").append(list);
/*  844 */             } else if (ruleEltName.equals("bymonth")) {
/*  845 */               String list = ruleElt.getAttribute("molist");
/*  846 */               recurBuf.append(";BYMONTH=").append(list);
/*  847 */             } else if (ruleEltName.equals("bysetpos")) {
/*  848 */               String list = ruleElt.getAttribute("poslist");
/*  849 */               recurBuf.append(";BYSETPOS=").append(list);
/*  850 */             } else if (ruleEltName.equals("wkst")) {
/*  851 */               String day = ruleElt.getAttribute("day");
/*  852 */               recurBuf.append(";WKST=").append(day);
/*  853 */             } else if (ruleEltName.equals("rule-x-name")) {
/*  854 */               String name = ruleElt.getAttribute("name", null);
/*  855 */               if (name != null) {
/*  856 */                 String value = ruleElt.getAttribute("value", "");
/*      */                 
/*      */ 
/*  859 */                 recurBuf.append(";").append(name).append("=").append(value);
/*      */               }
/*      */             }
/*      */           }
/*      */           try
/*      */           {
/*  865 */             ZRecur recur = new ZRecur(recurBuf.toString(), invTzMap);
/*  866 */             if (exclude) {
/*  867 */               subRules.add(new Recurrence.SimpleRepeatingRule(dtStart, dur, recur, null));
/*      */             } else {
/*  869 */               addRules.add(new Recurrence.SimpleRepeatingRule(dtStart, dur, recur, null));
/*      */             }
/*      */           } catch (ServiceException ex) {
/*  872 */             throw ServiceException.INVALID_REQUEST("Exception parsing <recur> <rule>", ex);
/*      */           }
/*      */         }
/*      */         else {
/*  876 */           throw ServiceException.INVALID_REQUEST("Expected <date> or <rule> inside of " + e.getName() + ", got " + intElt.getName(), null);
/*      */         }
/*      */       } }
/*      */     Element e;
/*      */     boolean exclude;
/*      */     Iterator intIter;
/*  882 */     if (recurId != null) {
/*  883 */       return new Recurrence.ExceptionRule(recurId, dtStart, dur, null, addRules, subRules);
/*      */     }
/*  885 */     return new Recurrence.RecurrenceRule(dtStart, dur, null, addRules, subRules);
/*      */   }
/*      */   
/*      */   static ParsedDateTime parseDtElement(Element e, TimeZoneMap tzMap, Invite inv)
/*      */     throws ServiceException
/*      */   {
/*  891 */     String d = e.getAttribute("d");
/*  892 */     String tzId = e.getAttribute("tz", null);
/*  893 */     ICalTimeZone timezone = null;
/*  894 */     if (tzId != null) {
/*  895 */       timezone = lookupAndAddToTzList(tzId, tzMap, inv);
/*      */     }
/*      */     try
/*      */     {
/*  899 */       return ParsedDateTime.parse(d, tzMap, timezone, inv.getTimeZoneMap().getLocalTimeZone());
/*      */     }
/*      */     catch (ParseException pe) {
/*  902 */       throw ServiceException.INVALID_REQUEST("Caught ParseException: " + pe, pe);
/*      */     }
/*      */   }
/*      */   
/*      */   static void parseTimeZones(Element parent, TimeZoneMap tzMap) throws ServiceException {
/*  907 */     assert (tzMap != null);
/*  908 */     for (Iterator iter = parent.elementIterator("tz"); iter.hasNext();) {
/*  909 */       Element tzElem = (Element)iter.next();
/*  910 */       ICalTimeZone tz = parseTzElement(tzElem);
/*  911 */       tzMap.add(tz);
/*      */     }
/*      */   }
/*      */   
/*      */ 
/*      */   public static ICalTimeZone parseTimeZone(CalTZInfoInterface calTZ)
/*      */     throws ServiceException
/*      */   {
/*  919 */     String tzid = calTZ.getId();
/*  920 */     if (null == calTZ.getTzStdOffset()) {
/*  921 */       throw ServiceException.INVALID_REQUEST("Unknown TZ: \"" + tzid + "\" and no " + "stdoff" + " specified", null);
/*      */     }
/*      */     
/*  924 */     int standardOffset = calTZ.getTzStdOffset().intValue();
/*  925 */     int daylightOffset = ((Integer)Objects.firstNonNull(calTZ.getTzDayOffset(), Integer.valueOf(standardOffset))).intValue();
/*      */     
/*  927 */     standardOffset *= 60000;
/*  928 */     daylightOffset *= 60000;
/*      */     
/*  930 */     ICalTimeZone.SimpleOnset standardOnset = null;
/*  931 */     ICalTimeZone.SimpleOnset daylightOnset = null;
/*  932 */     if (daylightOffset != standardOffset) {
/*  933 */       TzOnsetInfo standard = calTZ.getStandardTzOnset();
/*  934 */       TzOnsetInfo daylight = calTZ.getDaylightTzOnset();
/*  935 */       if ((standard == null) || (daylight == null)) {
/*  936 */         throw ServiceException.INVALID_REQUEST("DST time zone missing standard and/or daylight onset", null);
/*      */       }
/*      */       
/*  939 */       standardOnset = parseSimpleOnset(standard);
/*  940 */       daylightOnset = parseSimpleOnset(daylight);
/*      */     }
/*      */     
/*  943 */     String standardTzname = calTZ.getStandardTZName();
/*  944 */     String daylightTzname = calTZ.getDaylightTZName();
/*  945 */     return ICalTimeZone.lookup(tzid, standardOffset, standardOnset, standardTzname, daylightOffset, daylightOnset, daylightTzname);
/*      */   }
/*      */   
/*      */   private static ICalTimeZone.SimpleOnset parseSimpleOnset(TzOnsetInfo onsetInfo) throws ServiceException
/*      */   {
/*  950 */     int week = ((Integer)Objects.firstNonNull(onsetInfo.getWeek(), Integer.valueOf(0))).intValue();
/*  951 */     int wkday = ((Integer)Objects.firstNonNull(onsetInfo.getDayOfWeek(), Integer.valueOf(0))).intValue();
/*  952 */     if (null == onsetInfo.getMonth()) {
/*  953 */       throw ServiceException.INVALID_REQUEST("Timezone onset information missing month", null);
/*      */     }
/*  955 */     int month = onsetInfo.getMonth().intValue();
/*  956 */     int mday = ((Integer)Objects.firstNonNull(onsetInfo.getDayOfMonth(), Integer.valueOf(0))).intValue();
/*  957 */     int hour = ((Integer)Objects.firstNonNull(onsetInfo.getHour(), Integer.valueOf(0))).intValue();
/*  958 */     int minute = ((Integer)Objects.firstNonNull(onsetInfo.getMinute(), Integer.valueOf(0))).intValue();
/*  959 */     int second = ((Integer)Objects.firstNonNull(onsetInfo.getSecond(), Integer.valueOf(0))).intValue();
/*  960 */     return new ICalTimeZone.SimpleOnset(week, wkday, month, mday, hour, minute, second);
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   public static ICalTimeZone parseTzElement(Element tzElem)
/*      */     throws ServiceException
/*      */   {
/*  971 */     String tzid = tzElem.getAttribute("id");
/*  972 */     int standardOffset = (int)tzElem.getAttributeLong("stdoff");
/*      */     
/*  974 */     int daylightOffset = (int)tzElem.getAttributeLong("dayoff", standardOffset);
/*      */     
/*      */ 
/*  977 */     standardOffset *= 60000;
/*  978 */     daylightOffset *= 60000;
/*      */     
/*  980 */     ICalTimeZone.SimpleOnset standardOnset = null;
/*  981 */     ICalTimeZone.SimpleOnset daylightOnset = null;
/*  982 */     if (daylightOffset != standardOffset) {
/*  983 */       Element standard = tzElem.getOptionalElement("standard");
/*      */       
/*  985 */       Element daylight = tzElem.getOptionalElement("daylight");
/*      */       
/*  987 */       if ((standard == null) || (daylight == null)) {
/*  988 */         throw ServiceException.INVALID_REQUEST("DST time zone missing standard and/or daylight onset", null);
/*      */       }
/*      */       
/*  991 */       standardOnset = parseSimpleOnset(standard);
/*  992 */       daylightOnset = parseSimpleOnset(daylight);
/*      */     }
/*      */     
/*  995 */     String standardTzname = tzElem.getAttribute("stdname", null);
/*  996 */     String daylightTzname = tzElem.getAttribute("dayname", null);
/*      */     
/*  998 */     return ICalTimeZone.lookup(tzid, standardOffset, standardOnset, standardTzname, daylightOffset, daylightOnset, daylightTzname);
/*      */   }
/*      */   
/*      */   private static ICalTimeZone.SimpleOnset parseSimpleOnset(Element element) throws ServiceException
/*      */   {
/* 1003 */     int week = (int)element.getAttributeLong("week", 0L);
/* 1004 */     int wkday = (int)element.getAttributeLong("wkday", 0L);
/*      */     
/* 1006 */     int month = (int)element.getAttributeLong("mon");
/* 1007 */     int mday = (int)element.getAttributeLong("mday", 0L);
/* 1008 */     int hour = (int)element.getAttributeLong("hour");
/* 1009 */     int minute = (int)element.getAttributeLong("min");
/*      */     
/* 1011 */     int second = (int)element.getAttributeLong("sec");
/*      */     
/* 1013 */     return new ICalTimeZone.SimpleOnset(week, wkday, month, mday, hour, minute, second);
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   private static void parseInviteElementCommon(Account account, MailItem.Type type, Element element, Invite newInv, boolean recurrenceIdAllowed, boolean recurAllowed)
/*      */     throws ServiceException
/*      */   {
/* 1036 */     String invId = element.getAttribute("id", null);
/*      */     
/* 1038 */     Element compElem = element.getOptionalElement("comp");
/* 1039 */     if (compElem != null) {
/* 1040 */       element = compElem;
/*      */     }
/*      */     
/* 1043 */     String dts = element.getAttribute("d", null);
/*      */     
/* 1045 */     TimeZoneMap tzMap = newInv.getTimeZoneMap();
/* 1046 */     parseTimeZones(element.getParent(), tzMap);
/*      */     
/* 1048 */     newInv.setItemType(type);
/*      */     
/*      */ 
/* 1051 */     String uid = element.getAttribute("uid", null);
/* 1052 */     if ((uid != null) && (uid.length() > 0)) {
/* 1053 */       newInv.setUid(uid);
/*      */     }
/*      */     
/* 1056 */     if (recurrenceIdAllowed) {
/* 1057 */       Element e = element.getOptionalElement("exceptId");
/* 1058 */       if (e != null) {
/* 1059 */         ParsedDateTime dt = parseDateTime(e, tzMap);
/* 1060 */         RecurId recurId = new RecurId(dt, RecurId.RANGE_NONE);
/* 1061 */         newInv.setRecurId(recurId);
/*      */       }
/*      */     }
/* 1064 */     else if (element.getOptionalElement("exceptId") != null) {
/* 1065 */       throw ServiceException.INVALID_REQUEST("May not specify an <exceptId> in this request", null);
/*      */     }
/*      */     
/*      */ 
/*      */ 
/*      */ 
/* 1071 */     String name = element.getAttribute("name", "");
/* 1072 */     String location = element.getAttribute("loc", "");
/*      */     
/*      */ 
/* 1075 */     for (Iterator<Element> catIter = element.elementIterator("category"); catIter.hasNext();) {
/* 1076 */       String cat = ((Element)catIter.next()).getText();
/* 1077 */       newInv.addCategory(cat);
/*      */     }
/*      */     
/*      */ 
/* 1081 */     for (Iterator<Element> cmtIter = element.elementIterator("comment"); cmtIter.hasNext();) {
/* 1082 */       String cmt = ((Element)cmtIter.next()).getText();
/* 1083 */       newInv.addComment(cmt);
/*      */     }
/*      */     
/*      */ 
/* 1087 */     for (Iterator<Element> cnIter = element.elementIterator("contact"); cnIter.hasNext();) {
/* 1088 */       String contact = ((Element)cnIter.next()).getTextTrim();
/* 1089 */       newInv.addContact(contact);
/*      */     }
/*      */     
/*      */ 
/* 1093 */     Element geoElem = element.getOptionalElement("geo");
/* 1094 */     if (geoElem != null) {
/* 1095 */       Geo geo = Geo.parse(geoElem);
/* 1096 */       newInv.setGeo(geo);
/*      */     }
/*      */     
/*      */ 
/* 1100 */     String url = element.getAttribute("url", null);
/* 1101 */     newInv.setUrl(url);
/*      */     
/*      */ 
/* 1104 */     int seq = (int)element.getAttributeLong("seq", 0L);
/* 1105 */     newInv.setSeqNo(seq);
/*      */     
/*      */ 
/* 1108 */     newInv.setName(name);
/*      */     
/*      */ 
/* 1111 */     Element descElem = element.getOptionalElement("desc");
/* 1112 */     String desc = descElem != null ? descElem.getText() : null;
/* 1113 */     Element descHtmlElem = element.getOptionalElement("descHtml");
/* 1114 */     String descHtml = descHtmlElem != null ? descHtmlElem.getText() : null;
/* 1115 */     newInv.setDescription(desc, descHtml);
/*      */     
/* 1117 */     boolean allDay = element.getAttributeBool("allDay", false);
/* 1118 */     newInv.setIsAllDayEvent(allDay);
/*      */     
/*      */     Element startElem;
/*      */     Element startElem;
/* 1122 */     if (newInv.isTodo()) {
/* 1123 */       startElem = element.getOptionalElement("s");
/*      */     } else
/* 1125 */       startElem = element.getElement("s");
/* 1126 */     if (startElem != null) {
/* 1127 */       ParsedDateTime dt = parseDtElement(startElem, tzMap, newInv);
/*      */       
/* 1129 */       if ((allDay) && (dt.hasTime()))
/*      */       {
/* 1131 */         dt.setHasTime(false);
/* 1132 */       } else if ((!allDay) && (!dt.hasTime()))
/*      */       {
/*      */ 
/* 1135 */         allDay = true;
/* 1136 */         newInv.setIsAllDayEvent(allDay);
/*      */       }
/* 1138 */       newInv.setDtStart(dt);
/*      */     }
/*      */     
/*      */ 
/* 1142 */     Element endElem = element.getOptionalElement("e");
/* 1143 */     if (endElem != null) {
/* 1144 */       ParsedDateTime dt = parseDtElement(endElem, tzMap, newInv);
/*      */       
/* 1146 */       if ((allDay) && (dt.hasTime()))
/*      */       {
/* 1148 */         dt.setHasTime(false);
/* 1149 */       } else if ((!allDay) && (!dt.hasTime()))
/*      */       {
/*      */ 
/* 1152 */         allDay = true;
/* 1153 */         newInv.setIsAllDayEvent(allDay);
/*      */       }
/*      */       
/* 1156 */       if ((allDay) && (!newInv.isTodo()))
/*      */       {
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/* 1171 */         dt = dt.add(ParsedDuration.ONE_DAY);
/*      */       }
/* 1173 */       newInv.setDtEnd(dt);
/*      */     }
/*      */     else {
/* 1176 */       Element d = element.getOptionalElement("dur");
/* 1177 */       if (d != null) {
/* 1178 */         ParsedDuration pd = ParsedDuration.parse(d);
/* 1179 */         newInv.setDuration(pd);
/*      */       }
/*      */     }
/*      */     
/*      */ 
/* 1184 */     newInv.setLocation(location);
/*      */     
/*      */ 
/* 1187 */     String status = element.getAttribute("status", newInv.isEvent() ? "CONF" : "NEED");
/*      */     
/* 1189 */     validateAttr(IcalXmlStrMap.sStatusMap, "status", status);
/* 1190 */     newInv.setStatus(status);
/*      */     
/*      */ 
/* 1193 */     String classProp = element.getAttribute("class", "PUB");
/* 1194 */     validateAttr(IcalXmlStrMap.sClassMap, "class", classProp);
/* 1195 */     newInv.setClassProp(classProp);
/*      */     
/*      */ 
/* 1198 */     String priority = element.getAttribute("priority", null);
/* 1199 */     newInv.setPriority(priority);
/*      */     
/* 1201 */     if (newInv.isEvent())
/*      */     {
/* 1203 */       String fb = element.getAttribute("fb", null);
/* 1204 */       if (fb != null) {
/* 1205 */         newInv.setFreeBusy(fb);
/*      */         
/* 1207 */         if ("F".equals(fb)) {
/* 1208 */           newInv.setTransparency("T");
/*      */         } else {
/* 1210 */           newInv.setTransparency("O");
/*      */         }
/*      */       } else {
/* 1213 */         String transp = element.getAttribute("transp", "O");
/*      */         
/* 1215 */         validateAttr(IcalXmlStrMap.sTranspMap, "transp", transp);
/*      */         
/* 1217 */         newInv.setTransparency(transp);
/*      */         
/*      */ 
/*      */ 
/* 1221 */         if (newInv.isTransparent()) {
/* 1222 */           newInv.setFreeBusy("F");
/*      */         }
/*      */       }
/*      */     }
/* 1226 */     if (newInv.isTodo())
/*      */     {
/* 1228 */       String pctComplete = element.getAttribute("percentComplete", null);
/* 1229 */       newInv.setPercentComplete(pctComplete);
/*      */       
/*      */ 
/* 1232 */       String completed = element.getAttribute("completed", null);
/* 1233 */       if (completed != null) {
/*      */         try {
/* 1235 */           ParsedDateTime c = ParsedDateTime.parseUtcOnly(completed);
/* 1236 */           newInv.setCompleted(c.getUtcTime());
/*      */         } catch (ParseException e) {
/* 1238 */           throw ServiceException.INVALID_REQUEST("Invalid COMPLETED value: " + completed, e);
/*      */         }
/* 1240 */       } else if (status.equals("COMP")) {
/* 1241 */         newInv.setCompleted(System.currentTimeMillis());
/*      */       } else {
/* 1243 */         newInv.setCompleted(0L);
/*      */       }
/*      */     }
/*      */     
/*      */ 
/* 1248 */     boolean hasAttendees = false;
/* 1249 */     Iterator<Element> iter = element.elementIterator("at");
/* 1250 */     while (iter.hasNext()) {
/* 1251 */       ZAttendee at = ZAttendee.parse((Element)iter.next());
/* 1252 */       newInv.addAttendee(at);
/* 1253 */       hasAttendees = true;
/*      */     }
/* 1255 */     if ((hasAttendees) && (newInv.getMethod().equals(ZCalendar.ICalTok.PUBLISH.toString())))
/*      */     {
/* 1257 */       newInv.setMethod(ZCalendar.ICalTok.REQUEST.toString());
/*      */     }
/*      */     
/*      */ 
/* 1261 */     Element orgElt = element.getOptionalElement("or");
/*      */     
/* 1263 */     if (orgElt != null) {
/* 1264 */       ZOrganizer org = ZOrganizer.parse(orgElt);
/* 1265 */       newInv.setOrganizer(org);
/*      */     }
/*      */     
/*      */ 
/*      */ 
/* 1270 */     newInv.setIsOrganizer(account);
/*      */     
/* 1272 */     if (!newInv.isCancel())
/*      */     {
/*      */ 
/* 1275 */       boolean draft = element.getAttributeBool("draft", false);
/* 1276 */       newInv.setDraft(draft);
/*      */       
/*      */ 
/* 1279 */       boolean neverSent = element.getAttributeBool("neverSent", false);
/* 1280 */       newInv.setNeverSent(neverSent);
/*      */     }
/*      */     
/*      */ 
/* 1284 */     Element recur = element.getOptionalElement("recur");
/* 1285 */     if (recur != null) {
/* 1286 */       if (!recurAllowed) {
/* 1287 */         throw ServiceException.INVALID_REQUEST("No <recur> allowed in an exception", null);
/*      */       }
/*      */       
/*      */ 
/* 1291 */       ParsedDateTime st = newInv.getStartTime();
/* 1292 */       if (st == null) {
/* 1293 */         ParsedDateTime et = newInv.getEndTime();
/* 1294 */         if (et != null) {
/* 1295 */           if (et.hasTime()) {
/* 1296 */             st = et.add(ParsedDuration.NEGATIVE_ONE_SECOND);
/*      */           } else
/* 1298 */             st = et.add(ParsedDuration.NEGATIVE_ONE_DAY);
/* 1299 */           newInv.setDtStart(st);
/*      */         }
/*      */         else {
/* 1302 */           throw ServiceException.INVALID_REQUEST("recurrence used without DTSTART", null);
/*      */         }
/*      */       }
/* 1305 */       Recurrence.IRecurrence recurrence = parseRecur(recur, tzMap, newInv.getStartTime(), newInv.getEndTime(), newInv.getDuration(), newInv.getRecurId());
/*      */       
/*      */ 
/* 1308 */       newInv.setRecurrence(recurrence);
/*      */     }
/*      */     
/*      */ 
/* 1312 */     Iterator<Element> alarmsIter = element.elementIterator("alarm");
/* 1313 */     while (alarmsIter.hasNext()) {
/* 1314 */       Alarm alarm = Alarm.parse((Element)alarmsIter.next());
/* 1315 */       if (alarm != null) {
/* 1316 */         newInv.addAlarm(alarm);
/*      */       }
/*      */     }
/* 1319 */     List<ZCalendar.ZProperty> xprops = parseXProps(element);
/* 1320 */     for (ZCalendar.ZProperty prop : xprops) {
/* 1321 */       newInv.addXProp(prop);
/*      */     }
/* 1323 */     newInv.validateDuration();
/*      */     
/*      */ 
/* 1326 */     if (invId != null) {
/*      */       try {
/* 1328 */         int invIdInt = Integer.parseInt(invId);
/* 1329 */         newInv.setInviteId(invIdInt);
/*      */       }
/*      */       catch (NumberFormatException e) {}
/*      */     }
/*      */     
/* 1334 */     if (dts != null) {
/* 1335 */       newInv.setDtStamp(Long.parseLong(dts));
/*      */     }
/* 1337 */     Element fragment = element.getOptionalElement("fr");
/* 1338 */     if (fragment != null) {
/* 1339 */       newInv.setFragment(fragment.getText());
/*      */     }
/*      */   }
/*      */   
/*      */   public static List<ZCalendar.ZProperty> parseXProps(Element element) throws ServiceException {
/* 1344 */     List<ZCalendar.ZProperty> props = new ArrayList();
/* 1345 */     Iterator<Element> propIter = element.elementIterator("xprop");
/* 1346 */     while (propIter.hasNext()) {
/* 1347 */       Element propElem = (Element)propIter.next();
/* 1348 */       String propName = propElem.getAttribute("name");
/* 1349 */       String propValue = propElem.getAttribute("value", null);
/* 1350 */       ZCalendar.ZProperty xprop = new ZCalendar.ZProperty(propName);
/* 1351 */       xprop.setValue(propValue);
/* 1352 */       List<ZCalendar.ZParameter> xparams = CalendarUtil.parseXParams(propElem);
/* 1353 */       for (ZCalendar.ZParameter xparam : xparams) {
/* 1354 */         xprop.addParameter(xparam);
/*      */       }
/* 1356 */       props.add(xprop);
/*      */     }
/* 1358 */     return props;
/*      */   }
/*      */   
/*      */   public static List<CalendarItem.ReplyInfo> parseReplyList(Element element, TimeZoneMap tzMap) throws ServiceException
/*      */   {
/* 1363 */     List<CalendarItem.ReplyInfo> list = new ArrayList();
/* 1364 */     Iterator<Element> iter = element.elementIterator("reply");
/* 1365 */     while (iter.hasNext()) {
/* 1366 */       Element riElem = (Element)iter.next();
/* 1367 */       String addr = riElem.getAttribute("at");
/* 1368 */       ZAttendee at = new ZAttendee(addr);
/* 1369 */       String sentBy = riElem.getAttribute("sentBy", null);
/* 1370 */       if (sentBy != null)
/* 1371 */         at.setSentBy(sentBy);
/* 1372 */       String partStat = riElem.getAttribute("ptst", null);
/* 1373 */       if (partStat != null)
/* 1374 */         at.setPartStat(partStat);
/* 1375 */       int seq = (int)riElem.getAttributeLong("seq");
/* 1376 */       long dtStamp = riElem.getAttributeLong("d");
/* 1377 */       RecurId recurId = RecurId.fromXml(riElem, tzMap);
/* 1378 */       CalendarItem.ReplyInfo ri = new CalendarItem.ReplyInfo(at, seq, dtStamp, recurId);
/* 1379 */       list.add(ri);
/*      */     }
/* 1381 */     return list;
/*      */   }
/*      */   
/*      */   private static void validateAttr(IcalXmlStrMap map, String attrName, String value) throws ServiceException
/*      */   {
/* 1386 */     if (!map.validXml(value)) {
/* 1387 */       throw ServiceException.INVALID_REQUEST("Invalid value '" + value + "' specified for attribute:" + attrName, null);
/*      */     }
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */   public static Invite buildCancelInviteCalendar(Account acct, Account senderAcct, boolean asAdmin, boolean onBehalfOf, CalendarItem calItem, Invite inv, String comment, List<ZAttendee> forAttendees)
/*      */     throws ServiceException
/*      */   {
/* 1397 */     return cancelInvite(acct, senderAcct, asAdmin, onBehalfOf, calItem, inv, comment, forAttendees, null);
/*      */   }
/*      */   
/*      */ 
/*      */   public static Invite buildCancelInviteCalendar(Account acct, Account senderAcct, boolean asAdmin, boolean onBehalfOf, CalendarItem calItem, Invite inv, String comment)
/*      */     throws ServiceException
/*      */   {
/* 1404 */     return cancelInvite(acct, senderAcct, asAdmin, onBehalfOf, calItem, inv, comment, null, null);
/*      */   }
/*      */   
/*      */ 
/*      */   public static Invite buildCancelInstanceCalendar(Account acct, Account senderAcct, boolean asAdmin, boolean onBehalfOf, CalendarItem calItem, Invite inv, String comment, RecurId recurId)
/*      */     throws ServiceException
/*      */   {
/* 1411 */     return cancelInvite(acct, senderAcct, asAdmin, onBehalfOf, calItem, inv, comment, null, recurId);
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   static Invite cancelInvite(Account acct, Account senderAcct, boolean asAdmin, boolean onBehalfOf, CalendarItem calItem, Invite inv, String comment, List<ZAttendee> forAttendees, RecurId recurId)
/*      */     throws ServiceException
/*      */   {
/* 1453 */     boolean allowPrivateAccess = calItem.allowPrivateAccess(senderAcct, asAdmin);
/* 1454 */     return cancelInvite(acct, senderAcct, allowPrivateAccess, onBehalfOf, inv, comment, forAttendees, recurId, true);
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   private static Invite cancelInvite(Account acct, Account senderAcct, boolean asAdmin, boolean onBehalfOf, Folder folder, Invite inv, String comment, List<ZAttendee> forAttendees, RecurId recurId, boolean incrementSeq)
/*      */     throws ServiceException
/*      */   {
/* 1465 */     boolean allowPrivateAccess = CalendarItem.allowPrivateAccess(folder, senderAcct, asAdmin);
/* 1466 */     return cancelInvite(acct, senderAcct, allowPrivateAccess, onBehalfOf, inv, comment, forAttendees, recurId, incrementSeq);
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   private static Invite cancelInvite(Account acct, Account senderAcct, boolean allowPrivateAccess, boolean onBehalfOf, Invite inv, String comment, List<ZAttendee> forAttendees, RecurId recurId, boolean incrementSeq)
/*      */     throws ServiceException
/*      */   {
/* 1477 */     Invite cancel = new Invite(inv.getItemType(), ZCalendar.ICalTok.CANCEL.toString(), inv.getTimeZoneMap(), inv.isOrganizer());
/*      */     
/*      */ 
/*      */ 
/* 1481 */     if (inv.hasOrganizer()) {
/* 1482 */       ZOrganizer org = new ZOrganizer(inv.getOrganizer());
/* 1483 */       if ((onBehalfOf) && (senderAcct != null))
/* 1484 */         org.setSentBy(senderAcct.getName());
/* 1485 */       cancel.setOrganizer(org);
/*      */     }
/*      */     
/*      */ 
/* 1489 */     List<ZAttendee> attendees = forAttendees != null ? forAttendees : inv.getAttendees();
/*      */     
/* 1491 */     for (ZAttendee a : attendees) {
/* 1492 */       cancel.addAttendee(a);
/*      */     }
/* 1494 */     cancel.setClassProp(inv.getClassProp());
/* 1495 */     boolean showAll = (inv.isPublic()) || (allowPrivateAccess);
/* 1496 */     Locale locale = acct.getLocale();
/* 1497 */     if (!showAll)
/*      */     {
/* 1499 */       String sbj = L10nUtil.getMessage(L10nUtil.MsgKey.calendarSubjectWithheld, locale, new Object[0]);
/* 1500 */       cancel.setName(CalendarMailSender.getCancelSubject(sbj, locale));
/*      */     }
/*      */     else {
/* 1503 */       cancel.setName(CalendarMailSender.getCancelSubject(inv.getName(), locale));
/*      */       
/*      */ 
/* 1506 */       if ((comment != null) && (!comment.equals(""))) {
/* 1507 */         cancel.addComment(comment);
/*      */       }
/*      */     }
/*      */     
/* 1511 */     cancel.setUid(inv.getUid());
/*      */     
/*      */ 
/* 1514 */     if (inv.hasRecurId())
/*      */     {
/*      */ 
/* 1517 */       cancel.setRecurId(inv.getRecurId());
/*      */     }
/* 1519 */     else if (recurId != null) {
/* 1520 */       cancel.setRecurId(recurId);
/*      */     }
/*      */     
/*      */ 
/*      */ 
/* 1525 */     cancel.setIsAllDayEvent(inv.isAllDayEvent());
/*      */     
/*      */ 
/*      */ 
/* 1529 */     ParsedDateTime dtStart = recurId == null ? inv.getStartTime() : recurId.getDt();
/* 1530 */     if (dtStart != null) {
/* 1531 */       cancel.setDtStart(dtStart);
/* 1532 */       ParsedDuration dur = inv.getEffectiveDuration();
/* 1533 */       if (dur != null) {
/* 1534 */         cancel.setDtEnd(dtStart.add(dur));
/*      */       }
/*      */     }
/*      */     
/* 1538 */     cancel.setLocation(inv.getLocation());
/*      */     
/*      */ 
/* 1541 */     int seq = inv.getSeqNo();
/* 1542 */     if (incrementSeq)
/*      */     {
/*      */ 
/*      */ 
/* 1546 */       if ((acct != null) && (inv.isOrganizer()))
/* 1547 */         seq++;
/*      */     }
/* 1549 */     cancel.setSeqNo(seq);
/*      */     
/*      */ 
/* 1552 */     cancel.setStatus("CANC");
/*      */     
/*      */ 
/* 1555 */     cancel.setDtStamp(new Date().getTime());
/*      */     
/* 1557 */     return cancel;
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   public static void migrateAppointmentsAndTasks(Mailbox mbox)
/*      */     throws ServiceException
/*      */   {
/* 1569 */     List<Folder> folderList = mbox.getFolderList(null, SortBy.NONE);
/*      */     
/* 1571 */     for (Folder folder : folderList) {
/*      */       MailItem.Type type;
/*      */       TypedIdList idlist;
/*      */       int targetId;
/*      */       MailItem.Type type;
/* 1576 */       if (folder.getDefaultView() == MailItem.Type.APPOINTMENT)
/*      */       {
/* 1578 */         TypedIdList idlist = mbox.listCalendarItemsForRange(null, MailItem.Type.TASK, -1L, -1L, folder.getId());
/* 1579 */         int targetId = 15;
/* 1580 */         type = MailItem.Type.TASK;
/* 1581 */       } else { if (folder.getDefaultView() != MailItem.Type.TASK)
/*      */           continue;
/* 1583 */         idlist = mbox.listCalendarItemsForRange(null, MailItem.Type.APPOINTMENT, -1L, -1L, folder.getId());
/* 1584 */         targetId = 10;
/* 1585 */         type = MailItem.Type.APPOINTMENT;
/*      */       }
/*      */       
/*      */ 
/*      */ 
/* 1590 */       if (!idlist.isEmpty()) {
/* 1591 */         if (type == MailItem.Type.APPOINTMENT) {
/* 1592 */           ZimbraLog.calendar.info("Migrating " + idlist.size() + " Appointment(s) from '" + folder.getName() + "' to 'Calendar' folder for mailbox " + mbox.getId());
/*      */         }
/*      */         else {
/* 1595 */           ZimbraLog.calendar.info("Migrating " + idlist.size() + " Task(s) from '" + folder.getName() + "' to 'Tasks' folder for mailbox " + mbox.getId());
/*      */         }
/*      */         
/* 1598 */         int[] items = new int[idlist.size()];
/* 1599 */         int i = 0;
/* 1600 */         for (Integer id : idlist.getAllIds()) {
/* 1601 */           items[i] = id.intValue();
/* 1602 */           i++;
/*      */         }
/* 1604 */         mbox.move(null, items, type, targetId, null);
/*      */       }
/*      */     }
/*      */   }
/*      */   
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */ 
/*      */   public static boolean belongToSameAccount(String address1, String address2)
/*      */     throws ServiceException
/*      */   {
/* 1618 */     boolean isSameAccount = false;
/* 1619 */     if ((address1 != null) && (address2 != null))
/*      */     {
/* 1621 */       isSameAccount = address1.equalsIgnoreCase(address2);
/* 1622 */       if (!isSameAccount) {
/* 1623 */         Account acct = Provisioning.getInstance().get(Key.AccountBy.name, address1);
/* 1624 */         if (acct != null)
/*      */         {
/* 1626 */           AccountUtil.AccountAddressMatcher acctMatcher = new AccountUtil.AccountAddressMatcher(acct);
/* 1627 */           isSameAccount = acctMatcher.matches(address2);
/*      */         }
/*      */       }
/*      */     }
/* 1631 */     return isSameAccount;
/*      */   }
/*      */ }


/* Location:              /home/mint/zimbrastore.jar!/com/zimbra/cs/service/mail/CalendarUtils.class
 * Java compiler version: 7 (51.0)
 * JD-Core Version:       0.7.1
 */